<!DOCTYPE html>
<html lang="zh-CN">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>JAR Class 路径匹配工具</title>
    <style>
        * {
            margin: 0;
            padding: 0;
            box-sizing: border-box;
        }

        body {
            font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, 'Helvetica Neue', Arial, sans-serif;
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            min-height: 100vh;
            padding: 20px;
        }

        .container {
            max-width: 900px;
            margin: 0 auto;
            background: white;
            border-radius: 12px;
            box-shadow: 0 10px 40px rgba(0, 0, 0, 0.2);
            padding: 40px;
        }

        h1 {
            color: #333;
            margin-bottom: 10px;
            font-size: 28px;
        }

        .subtitle {
            color: #666;
            margin-bottom: 30px;
            font-size: 14px;
        }

        .upload-section {
            margin-bottom: 30px;
        }

        .upload-box {
            border: 2px dashed #ccc;
            border-radius: 8px;
            padding: 30px;
            text-align: center;
            background: #f9f9f9;
            transition: all 0.3s;
            cursor: pointer;
        }

        .upload-box:hover {
            border-color: #667eea;
            background: #f0f0ff;
        }

        .upload-box.dragover {
            border-color: #667eea;
            background: #e8e8ff;
        }

        input[type="file"] {
            display: none;
        }

        .upload-label {
            display: block;
            cursor: pointer;
            color: #667eea;
            font-weight: 500;
            margin-bottom: 10px;
        }

        .file-info {
            margin-top: 15px;
            font-size: 14px;
            color: #666;
        }

        .selected-file {
            display: inline-block;
            background: #e8e8ff;
            padding: 5px 10px;
            border-radius: 4px;
            margin: 5px;
            font-size: 13px;
        }

        .file-list {
            margin-top: 15px;
            display: flex;
            flex-direction: column;
            gap: 8px;
        }

        .file-item {
            display: flex;
            align-items: center;
            justify-content: space-between;
            background: #f8f9fa;
            padding: 10px 15px;
            border-radius: 6px;
            border: 1px solid #e0e0e0;
            transition: all 0.2s;
        }

        .file-item:hover {
            background: #f0f0ff;
            border-color: #667eea;
        }

        .file-name {
            flex: 1;
            font-size: 14px;
            color: #333;
            word-break: break-all;
        }

        .file-actions {
            display: flex;
            gap: 10px;
            align-items: center;
        }

        .btn-remove {
            background: #dc3545;
            color: white;
            border: none;
            padding: 5px 12px;
            border-radius: 4px;
            cursor: pointer;
            font-size: 12px;
            transition: background 0.2s;
        }

        .btn-remove:hover {
            background: #c82333;
        }

        .btn-add {
            background: #28a745;
            color: white;
            border: none;
            padding: 8px 16px;
            border-radius: 4px;
            cursor: pointer;
            font-size: 13px;
            margin-top: 10px;
            transition: background 0.2s;
        }

        .btn-add:hover {
            background: #218838;
        }

        .file-count {
            color: #666;
            font-size: 12px;
            margin-left: 10px;
        }

        .btn {
            background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
            color: white;
            border: none;
            padding: 12px 30px;
            border-radius: 6px;
            cursor: pointer;
            font-size: 16px;
            font-weight: 500;
            transition: transform 0.2s, box-shadow 0.2s;
            margin-top: 20px;
        }

        .btn:hover {
            transform: translateY(-2px);
            box-shadow: 0 5px 15px rgba(102, 126, 234, 0.4);
        }

        .btn:disabled {
            background: #ccc;
            cursor: not-allowed;
            transform: none;
        }

        .progress-section {
            margin-top: 30px;
            display: none;
        }

        .progress-section.active {
            display: block;
        }

        .progress-bar-container {
            width: 100%;
            height: 30px;
            background: #f0f0f0;
            border-radius: 15px;
            overflow: hidden;
            margin-bottom: 15px;
        }

        .progress-bar {
            height: 100%;
            background: linear-gradient(90deg, #667eea 0%, #764ba2 100%);
            width: 0%;
            transition: width 0.3s;
            display: flex;
            align-items: center;
            justify-content: center;
            color: white;
            font-size: 12px;
            font-weight: 500;
        }

        .progress-info {
            display: flex;
            justify-content: space-between;
            margin-bottom: 15px;
            font-size: 14px;
            color: #666;
        }

        .status {
            padding: 10px;
            border-radius: 6px;
            margin-top: 15px;
            font-size: 14px;
        }

        .status.processing {
            background: #fff3cd;
            color: #856404;
        }

        .status.completed {
            background: #d4edda;
            color: #155724;
        }

        .status.error {
            background: #f8d7da;
            color: #721c24;
        }

        .download-btn {
            background: #28a745;
            margin-top: 15px;
        }

        .download-btn:hover {
            box-shadow: 0 5px 15px rgba(40, 167, 69, 0.4);
        }

        .instructions {
            background: #e8f4f8;
            padding: 15px;
            border-radius: 6px;
            margin-bottom: 30px;
            font-size: 14px;
            color: #555;
        }

        .instructions h3 {
            margin-bottom: 10px;
            color: #333;
            font-size: 16px;
        }

        .instructions ul {
            margin-left: 20px;
            line-height: 1.8;
        }
    </style>
</head>
<body>
    <div class="container">
        <h1>🔍 JAR Class 路径匹配工具</h1>
        <p class="subtitle">上传JAR包和Class文件，自动匹配路径并导出Excel</p>

        <div class="instructions">
            <h3>使用说明：</h3>
            <ul>
                <li>上传一个JAR包文件</li>
                <li>上传一个或多个要匹配的文件（支持所有文件类型，支持同时选择多个）</li>
                <li>系统会自动在JAR包及其lib子目录中搜索匹配的文件（支持所有文件类型）</li>
                <li>处理完成后可下载包含匹配结果的Excel文件</li>
            </ul>
        </div>

        <form id="uploadForm">
            <div class="upload-section">
                <label class="upload-label">1. 上传JAR包文件</label>
                <div class="upload-box" id="jarUploadBox">
                    <input type="file" id="jarFile" name="jar_file" accept=".jar" required>
                    <label for="jarFile" class="upload-label">点击选择或拖拽JAR文件</label>
                    <div class="file-info" id="jarFileInfo"></div>
                </div>
            </div>

            <div class="upload-section">
                <label class="upload-label">2. 上传要匹配的文件（可多选，支持所有文件类型）</label>
                <div class="upload-box" id="classUploadBox">
                    <input type="file" id="classFiles" name="class_files" multiple>
                    <label for="classFiles" class="upload-label">点击选择或拖拽文件（可多选，支持所有类型）</label>
                    <div class="file-info" id="classFilesInfo"></div>
                    <div class="file-list" id="classFileList"></div>
                    <button type="button" class="btn-add" id="addClassFilesBtn" style="display: none;">继续添加文件</button>
                </div>
            </div>

            <button type="submit" class="btn" id="submitBtn">开始匹配</button>
        </form>

        <div class="progress-section" id="progressSection">
            <h3 style="margin-bottom: 15px; color: #333;">处理进度</h3>
            <div class="progress-info">
                <span id="progressText">准备中...</span>
                <span id="matchCount">匹配数: 0</span>
            </div>
            <div class="progress-bar-container">
                <div class="progress-bar" id="progressBar">0%</div>
            </div>
            <div class="status processing" id="statusDiv">处理中...</div>
            <button class="btn download-btn" id="downloadBtn" style="display: none;">下载Excel结果</button>
        </div>
    </div>

    <script>
        const uploadForm = document.getElementById('uploadForm');
        const jarFileInput = document.getElementById('jarFile');
        const classFilesInput = document.getElementById('classFiles');
        const submitBtn = document.getElementById('submitBtn');
        const progressSection = document.getElementById('progressSection');
        const progressBar = document.getElementById('progressBar');
        const progressText = document.getElementById('progressText');
        const matchCount = document.getElementById('matchCount');
        const statusDiv = document.getElementById('statusDiv');
        const downloadBtn = document.getElementById('downloadBtn');
        const jarFileInfo = document.getElementById('jarFileInfo');
        const classFilesInfo = document.getElementById('classFilesInfo');
        const classFileList = document.getElementById('classFileList');
        const addClassFilesBtn = document.getElementById('addClassFilesBtn');

        let currentTaskId = null;
        let progressInterval = null;
        let selectedClassFiles = []; // 存储已选择的Class文件

        // 文件选择处理
        jarFileInput.addEventListener('change', function() {
            if (this.files.length > 0) {
                jarFileInfo.innerHTML = `<span class="selected-file">${this.files[0].name}</span>`;
            }
        });

        // 更新Class文件列表显示
        function updateClassFileList() {
            if (selectedClassFiles.length === 0) {
                classFileList.innerHTML = '';
                classFilesInfo.innerHTML = '';
                addClassFilesBtn.style.display = 'none';
                return;
            }

            classFilesInfo.innerHTML = `<span class="selected-file">已选择 <strong>${selectedClassFiles.length}</strong> 个文件</span>`;
            addClassFilesBtn.style.display = 'block';

            // 清空列表
            classFileList.innerHTML = '';
            
            // 为每个文件创建列表项
            selectedClassFiles.forEach((file, index) => {
                const fileItem = document.createElement('div');
                fileItem.className = 'file-item';
                fileItem.setAttribute('data-index', index);
                
                const fileName = document.createElement('span');
                fileName.className = 'file-name';
                fileName.textContent = file.name;
                
                const fileActions = document.createElement('div');
                fileActions.className = 'file-actions';
                
                const fileCount = document.createElement('span');
                fileCount.className = 'file-count';
                fileCount.textContent = `${(file.size / 1024).toFixed(1)} KB`;
                
                const removeBtn = document.createElement('button');
                removeBtn.type = 'button';
                removeBtn.className = 'btn-remove';
                removeBtn.textContent = '删除';
                removeBtn.addEventListener('click', function() {
                    removeClassFile(index);
                });
                
                fileActions.appendChild(fileCount);
                fileActions.appendChild(removeBtn);
                
                fileItem.appendChild(fileName);
                fileItem.appendChild(fileActions);
                
                classFileList.appendChild(fileItem);
            });
        }

        // 添加文件（支持所有文件类型）
        function addClassFiles(files) {
            const allFiles = Array.from(files);
            allFiles.forEach(file => {
                // 检查是否已存在同名文件
                const exists = selectedClassFiles.some(f => f.name === file.name);
                if (!exists) {
                    selectedClassFiles.push(file);
                }
            });
            updateClassFileList();
            // 清空input，以便下次可以再次选择
            classFilesInput.value = '';
        }

        // 删除Class文件
        window.removeClassFile = function(index) {
            selectedClassFiles.splice(index, 1);
            updateClassFileList();
        };

        classFilesInput.addEventListener('change', function() {
            if (this.files.length > 0) {
                addClassFiles(this.files);
            }
        });

        // 继续添加文件按钮
        addClassFilesBtn.addEventListener('click', function() {
            classFilesInput.click();
        });

        // 拖拽支持
        const jarUploadBox = document.getElementById('jarUploadBox');
        const classUploadBox = document.getElementById('classUploadBox');

        [jarUploadBox, classUploadBox].forEach(box => {
            box.addEventListener('dragover', (e) => {
                e.preventDefault();
                box.classList.add('dragover');
            });

            box.addEventListener('dragleave', () => {
                box.classList.remove('dragover');
            });

            box.addEventListener('drop', (e) => {
                e.preventDefault();
                box.classList.remove('dragover');
                
                const files = e.dataTransfer.files;
                if (box === jarUploadBox && files.length > 0 && files[0].name.endsWith('.jar')) {
                    jarFileInput.files = files;
                    jarFileInfo.innerHTML = `<span class="selected-file">${files[0].name}</span>`;
                } else if (box === classUploadBox) {
                    const allFiles = Array.from(files);
                    if (allFiles.length > 0) {
                        addClassFiles(allFiles);
                    }
                }
            });
        });

        // 表单提交
        uploadForm.addEventListener('submit', async (e) => {
            e.preventDefault();

            const jarFile = jarFileInput.files[0];

            if (!jarFile) {
                alert('请选择JAR文件');
                return;
            }

            if (selectedClassFiles.length === 0) {
                alert('请至少添加一个文件');
                return;
            }

            const formData = new FormData();
            formData.append('jar_file', jarFile);
            for (let i = 0; i < selectedClassFiles.length; i++) {
                formData.append('class_files', selectedClassFiles[i]);
            }

            submitBtn.disabled = true;
            submitBtn.textContent = '上传中...';
            progressSection.classList.add('active');
            progressBar.style.width = '0%';
            statusDiv.className = 'status processing';
            statusDiv.textContent = '上传文件中...';
            downloadBtn.style.display = 'none';

            try {
                const response = await fetch('/upload', {
                    method: 'POST',
                    body: formData
                });

                const data = await response.json();

                if (!response.ok) {
                    throw new Error(data.error || '上传失败');
                }

                currentTaskId = data.task_id;
                startProgressCheck();
            } catch (error) {
                statusDiv.className = 'status error';
                statusDiv.textContent = '错误: ' + error.message;
                submitBtn.disabled = false;
                submitBtn.textContent = '开始匹配';
            }
        });

        // 开始进度检查
        function startProgressCheck() {
            if (progressInterval) {
                clearInterval(progressInterval);
            }

            progressInterval = setInterval(async () => {
                if (!currentTaskId) return;

                try {
                    const response = await fetch(`/progress/${currentTaskId}`);
                    const data = await response.json();

                    if (!response.ok) {
                        throw new Error(data.error || '获取进度失败');
                    }

                    updateProgress(data);
                } catch (error) {
                    console.error('获取进度错误:', error);
                    clearInterval(progressInterval);
                }
            }, 1000);
        }

        // 更新进度显示
        function updateProgress(data) {
            const { total, processed, matches, status } = data;

            if (status === 'completed') {
                clearInterval(progressInterval);
                progressBar.style.width = '100%';
                progressBar.textContent = '100%';
                progressText.textContent = '处理完成';
                matchCount.textContent = `匹配数: ${matches}`;
                statusDiv.className = 'status completed';
                statusDiv.textContent = '处理完成！可以下载结果了。';
                downloadBtn.style.display = 'block';
                submitBtn.disabled = false;
                submitBtn.textContent = '开始匹配';
            } else if (status.startsWith('error:')) {
                clearInterval(progressInterval);
                statusDiv.className = 'status error';
                statusDiv.textContent = '错误: ' + status.substring(7);
                submitBtn.disabled = false;
                submitBtn.textContent = '开始匹配';
            } else {
                const percentage = total > 0 ? Math.round((processed / total) * 100) : 0;
                progressBar.style.width = percentage + '%';
                progressBar.textContent = percentage + '%';
                progressText.textContent = `处理中... (${processed}/${total})`;
                matchCount.textContent = `匹配数: ${matches}`;
                statusDiv.className = 'status processing';
                statusDiv.textContent = '正在处理中，请稍候...';
            }
        }

        // 下载按钮
        downloadBtn.addEventListener('click', () => {
            if (currentTaskId) {
                window.location.href = `/download/${currentTaskId}`;
            }
        });
    </script>
</body>
</html>

